package animator.phantom.controller;

/*
    Copyright Janne Liljeblad

    This file is part of Phantom2D.

    Phantom2D is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    Phantom2D is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with Phantom2D.  If not, see <http://www.gnu.org/licenses/>.
*/

import java.util.*;
import java.awt.Dimension;
import java.io.File;

//--- Abstract base class for creating codec commands to encode movies.
//--- A extending class is created per every command line available encoding program.
public abstract class EncoderProgram
{
	protected String COMMAND;
	protected String codecProg;
	protected Vector<VideoFormat> formats = new Vector<VideoFormat>();

	private Vector<String> decodeFrameFormats = new Vector<String>();

	public static final int FROM_MULTIPLE_FILES = 0;
	public static final int FROM_SINGLE_FILE = 1;
	protected int mode = FROM_MULTIPLE_FILES;

	public static final String PNG = "png";
	public static final String JPEG = "jpeg";
	public static final String JPG = "jpg";
	public static final String TIFF = "tiff";

	protected String inputFrameExt;

	protected String format;

	public EncoderProgram( String command, String codecProg )
	{
		this.COMMAND = command;
		this.codecProg = codecProg;
	}

	//--- Initializes formats and codecs.
	public abstract void init();

	//--- Returns command used to encode movies. The main work method, others are meely to assist the work done here.
	//--- The command is in a form that it is mean to be run in the directory where the frames are.
	public abstract String getCommand();

	//--- Returns command used to decode movie files to frames if extending supports funtionality.
	public String getDecodeCommand(){ return null; }

	protected void addFormat( VideoFormat f ){ formats.add( f ); }
	public String[] getFormats()
	{
		int size = formats.size();
		String[] ret = new String[ size ];
		for( int i = 0; i < size; i++ )
			ret[ i ] = formats.elementAt( i ).getFormat();

		return ret;
	}
	
	//--- Current user settable encoding parameters. Used in extending classes getCommand() -method.
	protected VideoFormat format(){ return getFormat( CodecController.cFormat ); }
	protected String fileExtension(){ return format().getExtension(); }
	protected VideoCodec videoCodec(){ return format().vCodec(); }
	protected AudioCodec audioCodec(){ return format().aCodec(); }
	protected File inputFile(){ return CodecController.inputFile; }
	protected File outFolder(){ return RenderModeController.getTargetFolder(); }
	protected String movieName(){ return CodecController.movieFileName; }

	//--- Returns format for id string.
	public VideoFormat getFormat( String format )
	{
		int size = formats.size();
		for( int i = 0; i < size; i++ )
			if( formats.elementAt( i ).getFormat().equals( format ) ) return formats.elementAt( i );

		return null;
	}

	//--- this is just something from internet
	public int getDefaultVideoBitRatekbps()
	{
		return ((50 * 25 *  screensize().width * screensize().height) / 256)/ 1000;
	}

	public int getDefaultAudioBitRatekbps()
	{
		return 128;
	}

	public static Dimension screensize(){ return ProjectController.getScreenSize(); }
	public static int fps(){ return ProjectController.getFramesPerSecond(); }
	//--- NOTE: This only works if movie is rendered immediately after frames and targetFolder is not changed.
	//--- for any background render this will brake, and must be further developed.
	public static File framesFolder(){ return RenderModeController.getTargetFolder(); }
	//--- NOTE: Breaks for background render.
	public static String writeFrameType(){ return RenderModeController.getOutFrameType(); }

	public String getMoviePath()
	{
		return outFolder().getAbsolutePath() + "/" + movieName() + "." + fileExtension();
	}

	//--- decoding
	protected void addDecodeFrameFormat( String frameFormat ){ decodeFrameFormats.add( frameFormat ); }

	public String[] getDecodeFrameFormats()
	{
		int size = decodeFrameFormats.size();
		String[] ret = new String[ size ];
		for( int i = 0; i < size; i++ )
			ret[ i ] = decodeFrameFormats.elementAt( i );

		return ret;
	}

	public static String getDecodeMovie(){ return  CodecController.cDecodeMovie; }

	public static String getDecodeFrameFormat(){ return CodecController.cDecodeFrameFormat; }


}//end class
